<?php
/**
 * User: chenjin
 * Date: 2022/2/12
 * Time: 15:05
 */

namespace yi\web;

use Yi;

class Response extends \yi\base\Response
{
    const FORMAT_HTML = 'html';
    const FORMAT_JSON = 'json';
    public $formatters = [];
    private $_statusCode = 200;
    public $charset;

    private $_headers;
    public $data;
    public $contentType;

    public $format = self::FORMAT_HTML;
    public $content;
    private $statusText = 'ok';

    public function init()
    {
        if ($this->charset === null) {
            $this->charset = Yi::$app->charset;
        }

        //往formatters填充默认值
        $this->formatters = array_merge($this->defaultFormatters(), $this->formatters);
    }

    protected function defaultFormatters()
    {
        return [
            self::FORMAT_HTML => [
                'class' => 'yi\web\HtmlResponseFormatter',
            ],
            self::FORMAT_JSON => [
                'class' => 'yi\web\JsonResponseFormatter',
            ],
        ];
    }


    public function send()
    {
        $this->prepare();
        $this->sendHeaders();
        $this->sendContent();
    }

    protected function prepare()
    {
        if (isset($this->formatters[$this->format])) {
            $formatter = $this->formatters[$this->format];
            if (!is_object($formatter)) {
                $this->formatters[$this->format] = $formatter = Yi::createObject($formatter);
            }
            if ($formatter instanceof ResponseFormatterInterface) {
                $formatter->format($this);
            } else {
                throw new \Exception("The '{$this->format}' response formatter is invalid. It must implement the ResponseFormatterInterface.");
            }
        } else {
            throw new \Exception("Unsupported response format: {$this->format}");
        }
    }


    protected function sendHeaders()
    {
        if (headers_sent($file, $line)) {
            throw new \Exception("Headers already sent in {$file} on line {$line}.");
        }
        if ($this->_headers) {
            foreach ($this->getHeaders() as $name => $values) {
                $name = str_replace(' ', '-', ucwords(str_replace('-', ' ', $name)));
                // set replace for first occurrence of header but false afterwards to allow multiple
                $replace = true;
                foreach ($values as $value) {
                    header("$name: $value", $replace);
                    $replace = false;
                }
            }
        }
        $statusCode = $this->getStatusCode();
        header("HTTP/1.1 {$statusCode} {$this->statusText}");
    }

    protected function sendContent()
    {

        echo $this->content;
        return;
    }

    public function getHeaders()
    {
        if ($this->_headers === null) {
            $this->_headers = new HeaderCollection();
        }

        return $this->_headers;
    }

    public function getStatusCode()
    {
        return $this->_statusCode;
    }


}
